package leetcode.p726;

import java.util.*;

/**
 * @author: trtan
 * @date: 2021-07-05 18:39
 **/
public class NumberOfAtoms {
    /**
     * 大模拟+栈+枚举
     * @param formula
     * @return java.lang.String
     * @author trtan
     * @date 2021/7/5 19:45
     */
    public String countOfAtoms(String formula) {
        Stack<Map<String, Integer>> sta = new Stack<>();
        sta.push(new HashMap<>());
        for (int i = 0; i < formula.length(); i++) {
            char ch = formula.charAt(i);
            if (ch == '(') {
                sta.push(new HashMap<>());
            } else if (ch == ')') {
                Map<String, Integer> now = sta.pop();
                Map<String, Integer> pre = sta.peek();
                int base = 0;
                if (i + 1 < formula.length()) {
                    while (i + 1 < formula.length() && formula.charAt(i + 1) >= '0' && formula.charAt(i + 1) <= '9') {
                        base = base * 10 + (formula.charAt(i+1) - '0');
                        i++;
                    }
                }
                base = (base == 0 ? 1 : base);
                ArrayList<String> list = new ArrayList<>(now.keySet());
                for (int j = 0; j < list.size(); j++) {
                    String key = list.get(j);
                    Integer value = pre.getOrDefault(key, 0);
                    pre.put(key, value + now.getOrDefault(key, 0) * base);
                }
            } else {
                StringBuffer key = new StringBuffer("" + ch);
                // 获得一个完整字符串
                if (i + 1 < formula.length()) {
                    ch = formula.charAt(i + 1);
                    while (i + 1 < formula.length() && ch >= 'a' && ch <= 'z') {
                        key.append(ch);
                        i++;
                        if (i + 1 < formula.length()) {
                            ch = formula.charAt(i + 1);
                        }
                    }
                }
                int base = 0;
                // 看后续是否存在数字
                if (i + 1 < formula.length() && ch >= '0' && ch <= '9') {
                    while (i + 1 < formula.length() && formula.charAt(i + 1) >= '0' && formula.charAt(i + 1) <= '9') {
                        base = base * 10 + (formula.charAt(i+1) - '0');
                        i++;
                    }
                }
                base = (base == 0 ? 1 : base);
                Map<String, Integer> now = sta.peek();
                Integer value = now.getOrDefault(key.toString(), 0);
                System.out.println(key.toString() + ", " + (value + base));
                now.put(key.toString(), value + base);
            }
        }
        Map<String, Integer> peek = sta.peek();
        List<Map.Entry> list = new ArrayList<>(peek.entrySet());
        Collections.sort(list, (a, b) -> {
            String s1 = a.getKey().toString();
            String s2 = b.getKey().toString();
            return s1.compareTo(s2);
        });
        StringBuffer result = new StringBuffer();
        for (int i = 0; i < list.size(); i++) {
            Map.Entry entry = list.get(i);
            result.append(entry.getKey());
            int value = Integer.parseInt(entry.getValue().toString());
            if (value > 1) {
                result.append(value);
            }
        }
        return result.toString();
    }
}
